package com.example.mycomposelearing.dataobserval

import android.os.Bundle
import android.util.Log
import android.widget.Toast
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import androidx.compose.foundation.background
import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.*
import androidx.compose.foundation.lazy.LazyListState
import androidx.compose.foundation.rememberScrollState
import androidx.compose.material3.*
import androidx.compose.runtime.*
import androidx.compose.runtime.livedata.observeAsState
import androidx.compose.runtime.saveable.rememberSaveable
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.platform.LocalLifecycleOwner
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.lifecycle.*
import com.example.mycomposelearing.ui.theme.MyComposeLearingTheme
import kotlinx.coroutines.delay
import kotlinx.coroutines.launch

class ObserveDataActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            MyComposeLearingTheme {
                // A surface container using the 'background' color from the theme
                Surface(
                    modifier = Modifier.fillMaxSize(),
                    color = MaterialTheme.colorScheme.background
                ) {
                    GreetingMain("Android")
                }
            }
        }
    }


    private val mainViewModel: MainViewModel by lazy {
        ViewModelProvider(this).get(MainViewModel::class.java)
    }

    @Composable
    fun Greeting(name: String) {
        //从viewmodel中取出公有变量，并使用observeAsState实现响应式
        // 如果你学过vue，那么observeAsState的作用就类似于给变量套了个ref
        var count = mainViewModel.count.observeAsState()
        val countLazy by mainViewModel.count.observeAsState()
        var offset = remember("offsettgw") { mutableStateOf(count.value) }

        Column() {
            Log.d("tgw3", "Greeting: $offset")
            Text(text = "ViewModel 结合 remember 赋值使用$name!--${offset.value}", modifier = Modifier
                .padding(vertical = 6.dp)
                .background(Color.Blue)
                .padding(6.dp)
                .clickable {
                    mainViewModel.add()
                    offset.value = count.value
                })
            Text(text = "只取ViewModel的值 $name!--${count.value}", modifier = Modifier
                .padding(vertical = 6.dp)
                .background(Color.Blue)
                .padding(6.dp)
                .clickable {
                    mainViewModel.add()
                })

            Text(text = "只取remember的值 $name!--${offset.value}", modifier = Modifier
                .padding(vertical = 6.dp)
                .background(Color.Blue)
                .padding(6.dp)
                .clickable {
                    offset.value = (offset.value ?: 0) + 1
                })

            Text(text = "只取ViewModel的值 啊lazy模式直接就拿到值了$name!--${countLazy}", modifier = Modifier
                .padding(vertical = 6.dp)
                .background(Color.Blue)
                .padding(6.dp)
                .clickable {
                    mainViewModel.count.value = (mainViewModel.count.value ?: 0) + 1
                })
            //无效，因为在这个函数 取值 mainViewModel.composeCount.value ，所以整个Greeting会重建
//            upgradesState1(mainViewModel.composeCount.value){
//                mainViewModel.composeCountAdd()
//            }

            //有效，因为在这个函数 读值 mainViewModel.composeCount.value ，是在另一个函数中
            //尽可能延迟State的读行为
            Box(modifier = Modifier
                .padding(vertical = 6.dp)
                .background(Color.Blue)
                .padding(6.dp)
                .clickable {
                    mainViewModel.composeCountAdd()
                }) {

                upgradesState2() {
                    mainViewModel.composeCount.value ?: 0
                }
            }

            upgradesState()


            HelloContent()
        }
    }

    var value = 0
    @Composable
    fun GreetingMain(name: String) {
        var count = remember { mutableStateOf(0) }
        var countSaveable = rememberSaveable {mutableStateOf(StateManage1(0)) }

        var parentUpdate = remember() { mutableStateOf(0) }
        Log.d("tgw", "GreetingMain:开始测试生命周期${parentUpdate} ")

        Column {
            Log.d("tgw", "GreetingMain:开始测试生命周期 ")
            if (parentUpdate.value == 0) {
                testRemember()
                testLiveData()
            } else if (parentUpdate.value % 2 == 0) {
                testLiveData(parentUpdate.value)
                testStateFlowData()
                testSnapshotFlow()

            } else if (parentUpdate.value % 2 != 0) {
                testRemember()

            }

            //自己封装管理的
            val rememberStateManage = rememberStateManage(count)
            val rememberSaveableStateManage = rememberSaveableStateManage(countSaveable)
            rememberScrollState()
            LazyListState
            Text(
                text = "${rememberStateManage.state.value} 自己封装的stateStateManage", modifier = Modifier
                    .padding(vertical = 6.dp)
                    .background(Color.Red)
                    .padding(6.dp))
            Text(
                text = "${rememberSaveableStateManage.value.state}，横竖屏保留值 自己封装的 rememberSaveableStateManage", modifier = Modifier
                    .padding(vertical = 6.dp)
                    .background(Color.Red)
                    .padding(6.dp))

            val rememberUpdatedStateValue = rememberUpdatedState(newValue = count.value)
            DisposableEffect(rememberUpdatedStateValue) {
                Log.d("tgwDisposableEffect", "DisposableEffect:DisposableEffect ")

                onDispose {
                    Log.d("tgw", "testRemember:DisposableEffect onDispose ")

                }
            }
            MoviesScreen{
                Toast.makeText(this@ObserveDataActivity,"超时不会响应 LaunchedEffect",Toast.LENGTH_SHORT).show()
            }
            Log.d("tgw2", "testRemember:SideEffect ")

            SideEffect {
                Log.d("tgw", "testRemember:SideEffect ")
            }



//            testRemember( parentUpdate.value)
//            testLiveData( parentUpdate.value)
            Button(onClick = {
                count.value = count.value + 1
                value++
                rememberSaveableStateManage.value = StateManage1(1)
                parentUpdate.value = parentUpdate.value + 1
            }) {
                Text(
                    text = "$value 点击开始测试父类重组${parentUpdate.value}", modifier = Modifier
                        .padding(vertical = 6.dp)
                        .background(Color.Blue)
                        .padding(6.dp))
            }
        }
    }

    @Composable
    private fun testRemember(value: Int? = -1) {
        var countRemember = rememberSaveable { mutableStateOf(0) }
        Log.d("tgw", "testRemember: ${countRemember}")
        Text(text = "测试remember的更新方式$value--${mainViewModel.composeCount.value}",
            modifier = Modifier
                .padding(vertical = 6.dp)
                .background(Color.Blue)
                .padding(6.dp)
                .clickable {
//                countRemember.value = countRemember.value + 1
                    mainViewModel.composeCountAdd()
                })


        LaunchedEffect(Unit) {
            Log.d("tgw", "testRemember:LaunchedEffect ")
        }

        val lifecycleOwner = LocalLifecycleOwner.current

        DisposableEffect(Unit) {
            Log.d("tgw", "testRemember:DisposableEffect ")

            onDispose {
                Log.d("tgw", "testRemember:DisposableEffect onDispose ")

            }
        }
    }


    @Composable
    private fun testLiveData(parentValue: Int = -1) {
        var value = 1
        var countLiveData = mainViewModel.count.observeAsState()
        Log.d("tgw", "testLiveData: ")
        Text(text = "测试LiveData的更新方式传统值parentValue:$parentValue---：$value--${countLiveData.value}",
            modifier = Modifier
                .padding(vertical = 6.dp)
                .background(Color.Blue)
                .padding(6.dp)
                .clickable {
                    mainViewModel.add()
                    value = value++
                })
        Log.d("tgw", "testLiveData:LocalLifecycleOwner current ${LocalLifecycleOwner.current}")
        Log.d("tgw", "testLiveData:countLiveData ${countLiveData}")

        LaunchedEffect(Unit) {
            Log.d("tgw", "testLiveData:LaunchedEffect ")
        }

        val lifecycleOwner = LocalLifecycleOwner.current


        DisposableEffect(Unit) {
            Log.d("tgw", "testLiveData:DisposableEffect ")

            val observer = LifecycleEventObserver { source, event ->
                when (event) { //根据Event执行不同生命周期的操作
                    Lifecycle.Event.ON_CREATE -> {
                        Log.d("tgw", "testLiveData:DisposableEffect ON_CREATE")

                    }
                    Lifecycle.Event.ON_RESUME -> {
                        Log.d("tgw", "testLiveData:DisposableEffect ON_RESUME")

                    }
                    Lifecycle.Event.ON_PAUSE -> {
                        Log.d("tgw", "testLiveData:DisposableEffect ON_PAUSE")

                    }
                    Lifecycle.Event.ON_DESTROY -> {
                        Log.d("tgw", "testLiveData:DisposableEffect ON_DESTROY")

                    }
                    else -> {}
                }
            }
            lifecycleOwner.lifecycle.addObserver(observer)

            onDispose {
                Log.d("tgw", "testLiveData:DisposableEffect onDispose ")
                lifecycleOwner.lifecycle.removeObserver(observer)

            }
        }
    }


    //通过flow观测每一次的数据变更
    @Composable
    private fun testStateFlowData() {
        var value = 1
        val count = mainViewModel.sharedFlowCount.value
        var countflowData = mainViewModel.stateFlow.collectAsState()
        var sharedFlow = mainViewModel.sharedFlow.collectAsState(initial = 1)

        Log.d("tgw", "testLiveData: ")
        Text(text = "测试stateFlow的更新方式传统值parentValue:${countflowData.value}", modifier = Modifier
            .padding(vertical = 6.dp)
            .background(Color.Blue)
            .padding(6.dp)
            .clickable {
                mainViewModel.sendStateFlow(countflowData.value + 1)
            })



        val collectValue = -1
        DisposableEffect(Unit) {
//            mainViewModel.collectSharedFlow()
            lifecycleScope.launch {
//                mainViewModel.stateFlow.collect{
//                    println("tgw收集数据$it")
//
//                }
            }
            onDispose {
            }
        }
        Text(text = "测试sharedFlow的更新方式 这是事件吗传统值parentValue:${sharedFlow.value}", modifier = Modifier
            .padding(vertical = 6.dp)
            .background(Color.Blue)
            .padding(6.dp)
            .clickable {
                mainViewModel.sendSharedFlow(sharedFlow.value + 1)
            })
    }

    @Composable
    fun testSnapshotFlow() {
        val count = remember { mutableStateOf(0) }
        val countFlow = snapshotFlow { count.value }
        LaunchedEffect(countFlow) {
            countFlow.collect { value ->
                // Handle the new value
                Log.d("tgw", "MyComponent: ${value}")
            }

        }
        Button(onClick = { count.value++ }) { Text("testSnapshotFlow testSnapshotFlowClicked ${count.value} times") }
    }

    @Composable
    fun GreetingMainList(name: String) {
        //从viewmodel中取出公有变量，并使用observeAsState实现响应式
        // 如果你学过vue，那么observeAsState的作用就类似于给变量套了个ref
        var countLiveData = mainViewModel.countList.observeAsState()
        var countRemember = remember { mutableStateOf(arrayListOf(0, 1)) }

        Column() {
            Log.d("TAG", "GreetingMain:开始测试生命周期 ")

            Text(text = "测试remember的更新方式--${countRemember.value}", modifier = Modifier
                .padding(vertical = 6.dp)
                .background(Color.Blue)
                .padding(6.dp)
                .clickable {
//                    countRemember.value = countRemember.value + 1
                })


            Text(text = "测试LiveData的更新方式--${countLiveData.value}", modifier = Modifier
                .padding(vertical = 6.dp)
                .background(Color.Blue)
                .padding(6.dp)
                .clickable {
//                    mainViewModel.add()
                })

            Button(onClick = {
//                countRemember.value.add(3)

                mainViewModel.addList(3)
//                lifecycleScope.launch {
//                    delay(3000)
//                   countRemember.value.add(3)
//                    mainViewModel.add()
//                }
            }) {
                Text(
                    text = "点击开始测试", modifier = Modifier
                        .padding(vertical = 6.dp)
                        .background(Color.Blue)
                        .padding(6.dp)
                )
            }

            Log.d(
                "TAG",
                "GreetingMain:测试生命周期结束countRemember:${countRemember.value}-----countLiveData:${countLiveData.value} "
            )
        }
    }


    /**
     *状态升级 无效
     */
    @Composable
    private fun upgradesState1(value: Int?, click: (() -> Unit)? = null) {
        Text(text = "取mutableStateOf compose独有的值 ${value}", modifier = Modifier
            .padding(vertical = 6.dp)
            .background(Color.Blue)
            .padding(6.dp)
            .clickable {
                click?.invoke()
            })
    }

    /**
     *状态升级
     */
    @Composable
    private fun upgradesState2(value: () -> Int) {
        Text(text = "取mutableStateOf compose独有的值 ${value()}")
    }

    /**
     *状态升级
     */
    @Composable
    private fun upgradesState() {
        Text(text = "取mutableStateOf compose独有的值 ${mainViewModel.composeCount.value}",
            modifier = Modifier
                .padding(vertical = 6.dp)
                .background(Color.Blue)
                .padding(6.dp)
                .clickable {
                    mainViewModel.composeCountAdd()
                })
    }


    @Composable
    fun HelloContent() {
        var count by rememberSaveable { mutableStateOf(1) }

        Log.d("tgw1", "HelloContent: ")
//        HelloContent1(count = count, onCountChange = {
//            count = it
//        })

        HelloContent3(count = { count } , onCountChange = {
            count = it
        })
        Text(
            text = "Hello1",
            modifier = Modifier.padding(bottom = 8.dp),
        )
        Text(
            text = "Hello2",
            modifier = Modifier.padding(bottom = 8.dp),
        )
        Log.d("tgw1", "HelloContent: 值改变后--注释2---注释三发生重组")


//        Column(modifier = Modifier.padding(16.dp)) {
//            Text(
//                text = "HelloContent2",
//                modifier = Modifier.padding(bottom = 8.dp),
//            )
//            Log.d("tgw2", "HelloContent: ")
//            HelloContent2()
//        }
    }

    @Composable
    fun HelloScreen() {
        var name by rememberSaveable { mutableStateOf("") }
//   等价于     var name = rememberSaveable { mutableStateOf("") }.value
        Log.d("tgw1", "HelloScreen: ")
//        HelloContent3(name = { name }, onNameChange = {
//            name = it
//        })
        Text(
            text = "Hello1",
            modifier = Modifier.padding(bottom = 8.dp),
        )
        Text(
            text = "Hello2",
            modifier = Modifier.padding(bottom = 8.dp),
        )
        Log.d("tgw1", "HelloContent: 值改变后--注释2---注释三发生重组")

//        Column(modifier = Modifier.padding(16.dp)) {
//            Text(
//                text = "固定",
//                modifier = Modifier.padding(bottom = 8.dp),
//            )
//            Log.d("tgw2", "HelloScreen: ")
//            HelloContent2()
//        }
    }

    @Composable
    fun HelloContent1(count: Int, onCountChange: (Int) -> Unit) {
        Log.d("tgw11", "HelloContent: ")
        Column(modifier = Modifier.padding(16.dp)) {
            Text(
                text = "HelloContent1, $count",
                modifier = Modifier.padding(bottom = 8.dp),
            )
            Button(onClick = { onCountChange(count + 1) }) {
                Text(
                    text = "点击计数增加, $count",
                    modifier = Modifier.padding(bottom = 8.dp),
                )
            }

        }
    }

    @Composable
    fun HelloContent3(count: () -> Int, onCountChange: (Int) -> Unit) {
        Log.d("tgw31", "HelloContent: ")

        Column(modifier = Modifier.padding(16.dp)) {
            Text(
                text = "HelloContent1, ${count()}",
                modifier = Modifier.padding(bottom = 8.dp),
            )
            Button(onClick = { onCountChange(count() + 1) }) {
                Text(
                    text = "点击计数增加, ${count()}",
                    modifier = Modifier.padding(bottom = 8.dp),
                )
            }

        }
    }

    @Composable
    fun HelloContent2() {
        Log.d("tgw21", "HelloContent: ")

        Column(modifier = Modifier.padding(16.dp)) {
            Text(
                text = "Hello21",
                modifier = Modifier.padding(bottom = 8.dp),
            )

        }
    }

    /**
     *自动取消协成
     */
    @Composable
    fun MoviesScreen(click: () -> Unit) {

        // Creates a CoroutineScope bound to the MoviesScreen's lifecycle
        val scope = rememberCoroutineScope()


        val rememberUpdatedState by rememberUpdatedState("click")
        val remember by remember{ mutableStateOf("click1") }

        Button(
            onClick = {
                //不会取消
                lifecycleScope.launch{
                    delay(3000)
                    Toast.makeText(this@ObserveDataActivity,"普通的 不会取消协程的",Toast.LENGTH_SHORT).show()
                }

                // 会取消
                scope.launch {
                    delay(3000)
                    Toast.makeText(this@ObserveDataActivity,"点击事件延迟三秒",Toast.LENGTH_SHORT).show()
                }

            }
        ) {
            Text("rememberCoroutineScope ，开启的协成自动取消")

        }
        LaunchedEffect(remember){
            delay(2000)
            Toast.makeText(this@ObserveDataActivity,"重组会响应LaunchedEffect",Toast.LENGTH_SHORT).show()

        }
        LaunchedEffect(true){
            delay(2000)
            rememberUpdatedState

        }
    }

    @Preview(showSystemUi = true, showBackground = true)
    @Composable
    fun DefaultPreview() {
        MyComposeLearingTheme {
            Greeting("Android")
        }
    }

}

